import axios from 'axios'
import store from '../store/index'
import router from '../router/index'
import { Message, Loading } from 'element-ui'
import { getItem, setItem, getReqKey, getCacheUrl } from './useCache'
// import qs from 'qs'

let CancelToken = axios.CancelToken
// 缓存处理
const cacheAdapterEnhancer = (adapter, options) => {
	const { maxAge } = options
	return async config => {
		if (!(await getCacheUrl(config.url))) {
			return adapter(config)
		} else {
			const reqMaxAge = maxAge // 处理特殊的请求缓存时间
			const reqKey = getReqKey(config)
			const responseData = await getItem(reqKey)
			if (responseData) {
				return responseData[0]
			}
			const response = await adapter(config)
			if (response.status === 200) {
				const resData = JSON.parse(response.data)
				setItem(reqKey, [
					{ data: resData },
					{ createTime: new Date().getTime(), maxAge: reqMaxAge },
				])
				return response
			}
		}
	}
}
const http = axios.create({
	baseURL: '',
	adapter: cacheAdapterEnhancer(axios.defaults.adapter, {
		maxAge: 1000 * 60 * 60 * 24, // 默认缓存一天
	}),
})
http.defaults.timeout = 10000
http.defaults.withCredentials = true

if (process.env.NODE_ENV === 'production') {
	http.defaults.baseURL = '/api/'
} else {
	// http.defaults.baseURL = 'http://192.168.1.18:7801'
	http.defaults.baseURL = '/api/'
}

// 取消重复请求
// const pending = []
// const cancelToken = axios.CancelToken
// const removePending = config => {
//   for (const p in pending) {
//     if (pending[p].u === config.url.split('?')[0] + '&' + config.method) {
//       // 当当前请求在数组中存在时执行函数体
//       pending[p].f() // 执行取消操作
//       pending.splice(p, 1) // 数组移除当前请求
//     }
//   }
// }
let loadingOpt
/**
 * axios请求拦截器
 * @param {object} config axios请求配置对象
 * @return {object} 请求成功或失败时返回的配置对象或者promise error对象
 **/
http.interceptors.request.use(
	async config => {
		// removePending(config) // 在一个axios发送前执行一下取消操作
		// // eslint-disable-next-line new-cap
		// config.cancelToken = new cancelToken(c => {
		//   // pending存放每一次请求的标识，一般是url + 参数名 + 请求方法，当然你可以自己定义
		//   pending.push({ u: config.url.split('?')[0] + '&' + config.method, f: c }) // config.data为请求参数
		// })
		if (http.prototype._loading_) {
			loadingOpt = Loading.service({
				fullscreen: true,
				lock: true,
				text: '加载中...',
			})
		}
		const t = JSON.parse(window.localStorage.getItem('userMsg'))
		const token = store.state.user.userMsg.token || t ? t.token : ''
		if (token) {
			config.headers.Authorization = `${token}`
		}
		// const { url, params, data } = config
		// // const cacheUrl = await getItem('cacheUrlList')
		// // console.log(url, params, data)
		// const res = await getItem(url)
		// if (!res) {
		// 	if (params || data) {
		// 		setItem(url, params || data)
		// 	}
		// }
		return config
	},
	error => {
		if (http.prototype._loading_) {
			loadingOpt.close()
		}
		return Promise.reject(error || { data: {} })
	},
)

/**
 * axios 响应拦截器
 * @param {object} response 从服务端响应的数据对象或者error对象
 * @return {object} 响应成功或失败时返回的响应对象或者promise error对象
 **/
http.interceptors.response.use(
	response => {
		if (http.prototype._loading_) {
			// const loading = Loading.service({})
			loadingOpt.close()
		}
		http.prototype._loading_ = true
		const res = response.data?.head
		if (res?.code !== 200) {
			// debugger
			if (http.prototype._show_error_) {
				Message({
					message: res?.msg || '访问失败，请联系管理员',
					type: 'error',
					duration: 5 * 1000,
					showClose: true,
				})
			}
			if (res?.code === 401) {
				window.localStorage.setItem(
					'tabsList',
					JSON.stringify([
						{
							name: '首页',
							closable: false,
							isShow: true,
							componentName: 'Welcome',
							path: '/welcome',
						},
					]),
				)
				store.commit('user/CLEAR_USERMSG')
				store.commit('router/CLEAR_ADDROUTES')
				store.commit('common/CHANGE_TABSLIST')
				router.push({
					path: '/login',
				})
			}
			http.prototype_show_error_ = true
			return Promise.reject(response || { data: {} })
		} else {
			http.prototype_show_error_ = true
			return response || { data: {} }
		}
	},
	error => {
		if (http.prototype._loading_) {
			// const loading = Loading.service({})
			loadingOpt.close()
		}
		if (error.response) {
			if (error.response.status === 401) {
				store.commit('user/CLEAR_USERMSG')
				store.commit('router/CLEAR_ADDROUTES')
				router.replace({
					path: '/login',
				})
				Message({
					message: '登录超时，请重新登录',
					type: 'error',
					showClose: true,
				})
			} else if (
				error.response.status === 404 ||
				error.response.status === 500
			) {
				Message({
					message: '请求失败',
					type: 'error',
					showClose: true,
				})
			}
		} else {
			Message({
				message: '请求失败',
				type: 'error',
				showClose: true,
			})
		}
		http.prototype._show_error_ = true
		return Promise.reject(error?.response || { data: {} })
	},
)
http.prototype._loading_ = true
http.prototype._show_error_ = true
http.CancelToken = CancelToken
export default http
